package main

import "fmt"

// https://refactoringguru.cn/design-patterns/factory-method

type ButtonFactory interface {
	New() Button
}

type WinButtonFactory struct{}

func (*WinButtonFactory) New() Button {
	return new(WinButton)
}

type MacButtonFactory struct{}

func (*MacButtonFactory) New() Button {
	return new(MacButton)
}

////////////

type Button interface {
	Render()
}

type WinButton struct{}

func (b *WinButton) Render() {
	fmt.Println("render win button")
}

type MacButton struct{}

func (b *MacButton) Render() {
	fmt.Println("render mac button")
}

func main() {
	platfrom := "mac"

	var factory ButtonFactory
	switch platfrom {
	case "win":
		factory = new(WinButtonFactory)
	case "mac":
		factory = new(MacButtonFactory)
	default:
		panic("invalid")
	}

	b := factory.New()
	b.Render()
}
